﻿using System;
using System.Collections.Generic;
using System.Globalization;
using System.IO;
using System.Net;
using System.Net.Configuration;
using System.Net.Mail;
using SAS.Bussiness.Enum;
using SAS.Bussiness.SASServices;
using SAS.Core;
using SAS.Core.Entity;
using SAS.Core.Result;
using SAS.DataAccess;
using System.Linq;
namespace SAS.Bussiness
{
    public class WorkspaceBO : BaseBO
    {
        private const string EnpointServiceName = "wsEnpoint";

        #region Get workspace information

        /// <summary>
        /// Get workspaces summary
        /// </summary>
        /// <param name="user"></param>
        /// <param name="advSearch"></param>
        /// <param name="searchParameters"></param>
        /// <returns></returns>
        public SASResult<IList<WorkspaceSummary>> GetWorkspaces(User user, AdvSearch advSearch, SearchParameters searchParameters)
        {
            //create default for Business result
            SASResult<IList<WorkspaceSummary>> bussinessResult = new SASResult<IList<WorkspaceSummary>>
            {
                IsSucessful = false,
                Message = string.Empty,
                Result = new List<WorkspaceSummary>()
            };
            bussinessResult.OutputResult.Add("PageNumber", "0");
            bussinessResult.OutputResult.Add("PageSize", "0");
            bussinessResult.OutputResult.Add("ResultCount", "0");

            #region Validate
            //validate current logged in user.
            if (!ValidateCurrentUser(user, bussinessResult))
            {
                return bussinessResult;
            }

            if (advSearch == null)
            {
                bussinessResult.Message = "invalid calling service";
                return bussinessResult;
            }
            #endregion

            //Build SQL condition string from inputted searchParameters.
            //string condition = CreateSearchString(searchParameters);
            string condition = CreateCondition(searchParameters, advSearch.Paramvals);
            //Build order by condition string from order by column name and sorting expression.
            string sortCondition = String.Format("{0} {1}", advSearch.OrderBy, advSearch.Sord);

            //Call to DAL to get search result
            WorkspaceDAO workspaceDao = new WorkspaceDAO(user.TokenKey);
            SASResult<IList<WorkspaceSummary>> dataAccessResult = workspaceDao.GetSummary(advSearch.PageNumber, advSearch.PageSize, sortCondition, condition);


            //Validate data package
            if (dataAccessResult.IsSucessful)
            {
                bussinessResult.IsSucessful = true;
                bussinessResult.Result = dataAccessResult.Result;
                bussinessResult.OutputResult["PageNumber"] = advSearch.PageNumber.ToString(CultureInfo.InvariantCulture);
                bussinessResult.OutputResult["PageSize"] = advSearch.PageSize.ToString(CultureInfo.InvariantCulture);
                bussinessResult.OutputResult["ResultCount"] = dataAccessResult.Result.Count.ToString(CultureInfo.InvariantCulture);
            }
            else
            {
                bussinessResult.Message = dataAccessResult.Message;
            }


            //return business result
            return bussinessResult;
        }

        /// <summary>
        /// Get a workspace by workspace id
        /// </summary>
        /// <param name="user"></param>
        /// <param name="strWorkspaceId"></param>
        /// <returns></returns>
        public SASResult<WorkspaceDetail> GetWorkspace(User user, string strWorkspaceId)
        {
            return GetClientInformation(user, strWorkspaceId);
        }

        /// <summary>
        /// Get workspace information in SAS environment
        /// </summary>
        /// <param name="user"></param>
        /// <param name="strWorkspaceId"></param>
        /// <returns></returns>
        private SASResult<WorkspaceDetail> GetWorkspaceInformation(User user, string strWorkspaceId)
        {
            //create default for Business result
            SASResult<WorkspaceDetail> bussinessResult = new SASResult<WorkspaceDetail>
            {
                IsSucessful = false,
                Result = default(WorkspaceDetail)
            };

            #region Validate

            //validate current logged in user.
            if (!ValidateCurrentUser(user, bussinessResult))
            {
                return bussinessResult;
            }

            #endregion

            WorkspaceDetail emptyWorkspaceDetail = new WorkspaceDetail();

            string workspaceEmptyXml = Serialize(emptyWorkspaceDetail.Workspace);
            string clientEmptyXml = Serialize(emptyWorkspaceDetail.Client);
            string clientIOFileXml = Serialize(emptyWorkspaceDetail.ClientIOFile);

            int workspaceId = Int32.TryParse(strWorkspaceId, out workspaceId) ? workspaceId : 0;

            WorkspaceDAO workspaceDao = new WorkspaceDAO(user.TokenKey);
            SASResult<string> dataAccessResult = workspaceDao.Get(workspaceId, workspaceEmptyXml, clientEmptyXml, clientIOFileXml);

            if (!dataAccessResult.IsSucessful)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = "Cannot get workspace information to update";
                return bussinessResult;
            }


            string workspaceXmlData = dataAccessResult.OutputResult["WorkSpaceInfo"];
            string clientXmlData = dataAccessResult.OutputResult["ClientInfo"];
            string clientIOXmlData = dataAccessResult.OutputResult["ClientIOInfo"];
            string base64ImageData = dataAccessResult.OutputResult["ClientLogo"];

            WorkSpaceSchema workspaceSchema = DeSerialize<WorkSpaceSchema>(workspaceXmlData);
            ClientSchema clientSchema = DeSerialize<ClientSchema>(clientXmlData);
            ClientIOFileVarsSchema clientIOFileVarsSchema = DeSerialize<ClientIOFileVarsSchema>(clientIOXmlData);

            bussinessResult.IsSucessful = true;

            WorkspaceDetail workspaceDetail = new WorkspaceDetail
            {
                Workspace = workspaceSchema,
                Client = clientSchema,
                ClientIOFile = clientIOFileVarsSchema,
                ImageLogo = base64ImageData
            };

            bussinessResult.Result = workspaceDetail;

            return bussinessResult;
        }


        /// <summary>
        /// Get workspace information from SAS environment OR QA, DEV, PRO, UAT environment
        /// </summary>
        /// <param name="user"></param>
        /// <param name="strWorkspaceId"></param>
        /// <returns></returns>
        private SASResult<WorkspaceDetail> GetClientInformation(User user, string strWorkspaceId)
        {
            //create default for Business result
            SASResult<WorkspaceDetail> bussinessResult = new SASResult<WorkspaceDetail>
            {
                IsSucessful = false,
                Result = default(WorkspaceDetail)
            };

            #region Validate

            //validate current logged in user.
            if (!ValidateCurrentUser(user, bussinessResult))
            {
                return bussinessResult;
            }

            #endregion

            WorkspaceDetail emptyWorkspaceDetail = new WorkspaceDetail();
            string clientEmptyXml = Serialize(emptyWorkspaceDetail.Client);
            string clientEmptyIOFileXml = Serialize(emptyWorkspaceDetail.ClientIOFile);

            int workspaceId = Int32.TryParse(strWorkspaceId, out workspaceId) ? workspaceId : 0;

            SASResult<WorkspaceDetail> getWorkspaceResult = GetWorkspaceInformation(user, strWorkspaceId);

            if(!getWorkspaceResult.IsSucessful)
            {
                bussinessResult.Message =getWorkspaceResult.Message;
                return bussinessResult;
            }

            WorkspaceDetail workspaceDetail = getWorkspaceResult.Result;
            bussinessResult.Result = workspaceDetail;
                 
            //If workspace is deployed PRO, DEV, UAT, QA environment(the status is 'activated' - 'activated without striata')
            //--> Get workspace information from that environment
            if (String.CompareOrdinal(workspaceDetail.Workspace.WorkSpaceStatusName, WorkspaceStatus.Activated) == 0 ||
                String.CompareOrdinal(workspaceDetail.Workspace.WorkSpaceStatusName,
                                      WorkspaceStatus.ActiveWithoutStriata) == 0)
            {
                TargetEnvironmentDAO targetEnvironmentDAO = new TargetEnvironmentDAO(user.TokenKey);

                SASResult<string> targetEnvironmentNameByWorkspace = targetEnvironmentDAO.Get(workspaceDetail.Workspace.pkWorkSpace_ID);
                //validate targetEnvironmentNameByWorkspace
                if (!targetEnvironmentNameByWorkspace.IsSucessful)
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message = "Cannot get target environment information";
                    bussinessResult.Result = null;
                    return bussinessResult;
                }

                string targetEnvironmentName = targetEnvironmentNameByWorkspace.OutputResult["TargetEnvironment"];

                //Get target environment service URL.
                SASResult<Core.Entity.Environment> environmentResult = GetEnvironment(user, targetEnvironmentName);
                //validate get target environment URL result
                if (!environmentResult.IsSucessful)
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message = environmentResult.Message;
                    return bussinessResult;
                }

                try
                {
                    //Get environment service URL from environment result
                    string environmentServiceURL = environmentResult.Result.ServiceUrl;

                    //Initialize environment service
                    SASServiceClient environmentService = new SASServiceClient(EnpointServiceName, environmentServiceURL);

                    #region 1. Get workspace(client) from environment

                    string clientId = workspaceDetail.Client.ClientID.ToString(CultureInfo.InvariantCulture);
                    SASResultOfstring clientInfoFromEnvironment = environmentService.GetClient(user.DisplayName,
                                                                                               clientId,
                                                                                               clientEmptyXml,
                                                                                               clientEmptyIOFileXml);

                    //validate result
                    if (!clientInfoFromEnvironment.IsSucessful)
                    {
                        bussinessResult.IsSucessful = false;
                        bussinessResult.Message = clientInfoFromEnvironment.Message;
                        bussinessResult.Result = null;
                        return bussinessResult;
                    }

                    //get client information as XML string from client result
                    string clientXMLResult = clientInfoFromEnvironment.OutputResult["ClientXML"];
                    string clientIOXML = clientInfoFromEnvironment.OutputResult["ClientIOXML"];
                    string imageBase64 = clientInfoFromEnvironment.OutputResult["ImageContent"];

                    //Deserialize to client - clientIO object
                    ClientSchema clientObj = DeSerialize<ClientSchema>(clientXMLResult);
                    ClientIOFileVarsSchema clientIO = DeSerialize<ClientIOFileVarsSchema>(clientIOXML);

                    workspaceDetail.Client = clientObj;
                    workspaceDetail.ClientIOFile = clientIO;
                    workspaceDetail.ImageLogo = imageBase64;

                    #endregion
                }
                catch (Exception serviceException)
                {
                    Log(serviceException);
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message =
                        String.Format("The Environment service is not ready for get client information function");
                    return bussinessResult;
                }
                
            }

            bussinessResult.IsSucessful = true;
            return bussinessResult;
        }

        #endregion

        #region Add - Update - Active workspace

        /// <summary>
        /// Add new workspace to SAS environment
        /// </summary>
        /// <param name="user"></param>
        /// <param name="workspaceDetail"></param>
        /// <param name="defaultLogoPath"></param>
        /// <returns></returns>
        public SASResult<string> AddNewWorkspace(User user, WorkspaceDetail workspaceDetail, string defaultLogoPath)
        {
            if (workspaceDetail.Client.LogoFileStream !=  null &&
                workspaceDetail.Client.LogoFileStream.Length > 102400)
            {
                return new SASResult<string>
                    {
                        IsSucessful = false,
                        Message = "Image size must be less than 100kb"
                    };
            }

            //Status for workspace is "SAVED"
            workspaceDetail.Workspace.WorkSpaceStatusName = WorkspaceStatus.Saved;
            //All new workspace will come in to SAS
            workspaceDetail.Workspace.EnvironmentName = EnvironmentName.SASEnvironment;

            workspaceDetail.Workspace.CreatedBy = user.DisplayName;
            workspaceDetail.Workspace.CreatedDate = DateTime.Now;

            workspaceDetail.Workspace.pkWorkSpace_ID = "0";
            workspaceDetail.Client.pkClient_ID = "0";
            workspaceDetail.ClientIOFile.fkClient_ID = "0";

            //Validate and save to database
            return Save(user, workspaceDetail, defaultLogoPath);
        }

        /// <summary>
        /// update workspace information
        /// </summary>
        /// <param name="user"></param>
        /// <param name="workspaceDetail"></param>
        /// <param name="defaultLogoPath"></param>
        /// <returns></returns>
        public SASResult<string> UpdateWorkspace(User user, WorkspaceDetail workspaceDetail, string defaultLogoPath)
        {
            //create default for Business result
            SASResult<string> bussinessResult = new SASResult<string>
            {
                IsSucessful = false,
                Result = string.Empty
            };
            #region Validate

            //validate current logged in user.
            if (!ValidateCurrentUser(user, bussinessResult))
            {
                return bussinessResult;
            }

            if (workspaceDetail.Client.LogoFileStream != null &&
                workspaceDetail.Client.LogoFileStream.Length > 102400)
            {
                return new SASResult<string>
                {
                    IsSucessful = false,
                    Message = "Image size must be less than 100kb"
                };
            }

            #endregion

            SASResult<WorkspaceDetail> workspaceResult = GetWorkspaceInformation(user, workspaceDetail.Workspace.pkWorkSpace_ID);
            //validate get workspace information.
            if (!workspaceResult.IsSucessful ||
                workspaceResult.Result == null)
            {
                bussinessResult.IsSucessful = true;
                bussinessResult.Message = "Cannot get workspace information to update";
                return bussinessResult;
            }

            if (String.CompareOrdinal(workspaceResult.Result.Workspace.WorkSpaceStatusName, WorkspaceStatus.Activated) == 0 ||
               String.CompareOrdinal(workspaceResult.Result.Workspace.WorkSpaceStatusName, WorkspaceStatus.ActiveWithoutStriata) == 0)
            {
                workspaceResult = GetClientInformation(user, workspaceDetail.Workspace.pkWorkSpace_ID);
            }
            if (!workspaceResult.IsSucessful ||
                workspaceResult.Result == null)
            {
                bussinessResult.IsSucessful = true;
                bussinessResult.Message = "Cannot get client information to update";
                return bussinessResult;
            }

            workspaceDetail.Workspace.WorkSpaceStatusName = workspaceResult.Result.Workspace.WorkSpaceStatusName;
            workspaceDetail.Workspace.EnvironmentName = workspaceResult.Result.Workspace.EnvironmentName;

            if (workspaceDetail.Client.LogoFileStreamSize == 0)
            {
                workspaceDetail.ImageLogo = workspaceResult.Result.ImageLogo;
            }

            //Can not save change with completed status.
            if (String.CompareOrdinal(workspaceDetail.Workspace.WorkSpaceStatusName, WorkspaceStatus.Completed) == 0)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = "Selected workspace is completed, can not update information";
                return bussinessResult;
            }
            if (String.CompareOrdinal(workspaceDetail.Workspace.WorkSpaceStatusName, WorkspaceStatus.Saved) == 0 ||
                String.CompareOrdinal(workspaceDetail.Workspace.WorkSpaceStatusName, WorkspaceStatus.CloneSaved) == 0)
            {
                //Validate and save to SAS database
                bussinessResult = Save(user, workspaceDetail, defaultLogoPath);
                return bussinessResult;
            }

            if (String.CompareOrdinal(workspaceDetail.Workspace.WorkSpaceStatusName, WorkspaceStatus.Activated) == 0 ||
                String.CompareOrdinal(workspaceDetail.Workspace.WorkSpaceStatusName, WorkspaceStatus.ActiveWithoutStriata) == 0)
            {
                //1 --> Save to Environment
                //2 --> Save to SAS database

                if (String.IsNullOrEmpty(workspaceDetail.ClientIOFile.ClientShortName) ||
                      String.IsNullOrEmpty(workspaceDetail.ClientIOFile.StriataServerNameOrIP) ||
                      String.IsNullOrEmpty(workspaceDetail.ClientIOFile.StriataServerDesc) ||
                      String.IsNullOrEmpty(workspaceDetail.ClientIOFile.StriataUsername) ||
                      String.IsNullOrEmpty(workspaceDetail.ClientIOFile.FedPayServerNameOrIP) ||
                      String.IsNullOrEmpty(workspaceDetail.ClientIOFile.FedPayServerDesc) ||
                      String.IsNullOrEmpty(workspaceDetail.ClientIOFile.FedPayUsername))
                {
                    workspaceDetail.Workspace.WorkSpaceStatusName = WorkspaceStatus.ActiveWithoutStriata;
                }
                else
                {
                    workspaceDetail.Workspace.WorkSpaceStatusName = WorkspaceStatus.Activated;
                }


                #region Detect target service URL

                TargetEnvironmentDAO targetEnvironmentDAO = new TargetEnvironmentDAO(user.TokenKey);
                SASResult<string> targetEnvironmentResult = targetEnvironmentDAO.Get(workspaceDetail.Workspace.pkWorkSpace_ID);

                //validate get targetEnvironmentResult
                if (!targetEnvironmentResult.IsSucessful ||
                    !targetEnvironmentResult.OutputResult.ContainsKey("TargetEnvironment") ||
                     String.IsNullOrEmpty(targetEnvironmentResult.OutputResult["TargetEnvironment"]))
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message = "can not get target workspace information";
                    return bussinessResult;
                }

                string targetEnvironmentName = targetEnvironmentResult.OutputResult["TargetEnvironment"];

                SASResult<Core.Entity.Environment> environmentResult = GetEnvironment(user, targetEnvironmentName);
              
                //Validate get target environment service URL
                if(!environmentResult.IsSucessful ||
                    String.IsNullOrEmpty(environmentResult.Result.ServiceUrl))
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message = "Can not get target service URL to update";
                    return bussinessResult;
                }

                //Detect environment service URL
                string environmentServiceURL = environmentResult.Result.ServiceUrl;
                #endregion

                if (!String.IsNullOrEmpty(environmentServiceURL))
                {
                    #region 1. Save to environment
                    try
                    {
                        workspaceDetail = DetectInformation(workspaceDetail);
                        workspaceDetail.Client.CreatedBy = user.DisplayName;
                        workspaceDetail.Client.ModifiedBy = user.DisplayName;

                        //Create service Client call
                        SASServiceClient environmentService = new SASServiceClient(EnpointServiceName, environmentServiceURL);

                        //Call to update client information in environment
                        SASResultOfstring saveClientResult = environmentService.SaveClient(user.DisplayName,
                                                                                           workspaceDetail.Client.ClientID.ToString(CultureInfo.InvariantCulture),
                                                                                           Serialize(workspaceDetail.Client),
                                                                                           Serialize(workspaceDetail.ClientIOFile),
                                                                                           workspaceDetail.ImageLogo);

                        //validate save client action
                        if (!saveClientResult.IsSucessful)
                        {
                            bussinessResult.IsSucessful = false;
                            bussinessResult.Message = saveClientResult.Message;
                            return bussinessResult;
                        }
                    }
                    catch (Exception serviceException)
                    {
                        Log(serviceException);
                        bussinessResult.IsSucessful = false;
                        bussinessResult.Message = String.Format("The Environment Service is not ready for update function");
                        return bussinessResult;
                    }
                    #endregion

                    #region Save workspace information to SAS Environment

                   var workspaceInfo =  GetWorkspaceInformation(user, workspaceDetail.Workspace.pkWorkSpace_ID);
                    //save new Workspace note if user change
                    workspaceInfo.Result.Workspace.WorkSpaceNote = workspaceDetail.Workspace.WorkSpaceNote;
                    //save new Workspace name if user change
                    workspaceInfo.Result.Workspace.WorkSpaceName = workspaceDetail.Workspace.WorkSpaceName;
                    //update workspace status
                    workspaceInfo.Result.Workspace.WorkSpaceStatusName = workspaceDetail.Workspace.WorkSpaceStatusName;

                    //Update workspace to SAS database
                    SASResult<string> saveResult = Save(user, workspaceInfo.Result, defaultLogoPath);
                    //validate save to SAS database result
                    if (!saveResult.IsSucessful)
                    {
                        bussinessResult.IsSucessful = false;
                        bussinessResult.Message = String.Format("Can not save to SAS Environment");
                        return bussinessResult;
                    }

                    #endregion
                }
                else
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message = "Can not detect environment information";
                    return bussinessResult;
                }

                bussinessResult.IsSucessful = true;
            }


            return bussinessResult;
        }

        /// <summary>
        /// Active a workspace to target environment.
        /// </summary>
        /// <param name="user"></param>
        /// <param name="workspaceDetail"></param>
        /// <param name="enviromentName"></param>
        /// <param name="defaultLogoPath"></param>
        /// <returns></returns>
        public SASResult<string> Activate(User user, WorkspaceDetail workspaceDetail, string enviromentName, string defaultLogoPath)
        {
            //create default for Business result
            SASResult<string> bussinessResult = new SASResult<string>
            {
                IsSucessful = true,
                Result = string.Empty
            };


            #region Validate

            //validate current logged in user.
            if (!ValidateCurrentUser(user, bussinessResult))
            {
                return bussinessResult;
            }
            if(workspaceDetail == null)
            {
                bussinessResult.IsSucessful = true;
                bussinessResult.Message = "Cannot get workspace information";
                return bussinessResult;
            }

            if (workspaceDetail.Client.LogoFileStream != null &&
                workspaceDetail.Client.LogoFileStream.Length > 102400)
            {
                return new SASResult<string>
                {
                    IsSucessful = false,
                    Message = "Image size must be less than 100kb"
                };
            }

            #endregion

            #region If workspace status is COMPLETED --> Load workspace detail information from SAS Environment

            //Due to read only mode in web application, the information of workspace must be loaded from SAS environment.
            if (!String.IsNullOrEmpty(workspaceDetail.Workspace.pkWorkSpace_ID) ||
                String.CompareOrdinal(workspaceDetail.Workspace.pkWorkSpace_ID, "0") != 0)
            {
                SASResult<WorkspaceDetail> workspaceDetailResult = GetClientInformation(user, workspaceDetail.Workspace.pkWorkSpace_ID);
                if (workspaceDetailResult.IsSucessful)
                {
                    if (String.CompareOrdinal(workspaceDetailResult.Result.Workspace.WorkSpaceStatusName, WorkspaceStatus.Completed) == 0)
                    {
                        workspaceDetail = workspaceDetailResult.Result;
                    }

                    if(String.IsNullOrEmpty(workspaceDetail.ImageLogo) &&
                        (workspaceDetail.Client.LogoFileStream == null || workspaceDetail.Client.LogoFileStream.Length == 0))
                    {
                        workspaceDetail.ImageLogo = workspaceDetailResult.Result.ImageLogo;
                    }
                }
                else
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message = "Can not load client information";

                    return bussinessResult;
                }
            }

            #endregion

            #region Documentation flow
            //      User story: Creating admin login credentials after workspace activation
            //1.	User clicks on a SAS record which is in SAVED status
            //2.	Workspace details screen shows the record in its current state. Admin user and password fields are blank.
            //3.	User enters all the fields required to activate a client workspace and clicks on the activate button.
            //4.	User is presented with a dialog box that prompts the user to select a target environment, the user makes a selection and clicks Ok.
            //a.	The web application will call a Stored proc in SAS to save the current state of the record. The SAS record is now in COMPLETED status
            //b.	The web application will invoke a web method on the target environment web service to activate a record.
            //i.	The web method will return a string value which will contain the admin user id and password.
            //ii.	The web application will create another workspace row in the SAS database to display the newly created workspace with status ACTIVATED.
            //c.	The web application will use the return value from the web method and invoke another stored proc on SAS to update Admin User id and password in the record which was marked completed in step a.
            #endregion

            #region 1. Call to service environment to add new client - save the logo - active that client

            workspaceDetail = DetectInformation(workspaceDetail);

            
            //Set default logo
            if (String.IsNullOrEmpty(workspaceDetail.ImageLogo))
            {
                MemoryStream memoryStream = new MemoryStream(File.ReadAllBytes(defaultLogoPath));
                workspaceDetail.ImageLogo = ImageStreamToBase64(memoryStream, Path.GetFileName(defaultLogoPath), (int)memoryStream.Length);
            }

            SASResult<Core.Entity.Environment> environmentResult = GetEnvironment(user, enviromentName);
            //validate get target environment URL result
            if (!environmentResult.IsSucessful)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = environmentResult.Message;
                return bussinessResult;
            }

            //Detect environment service URL
            string environmentServiceURL = environmentResult.Result.ServiceUrl;

            //Initialize environment service
            SASServiceClient environmentService = new SASServiceClient(EnpointServiceName, environmentServiceURL);

            try
            {
                #region Add new client information to target environment

                //update client information.
                workspaceDetail.Client.pkClient_ID = "0";
                workspaceDetail.Client.CreatedBy = user.DisplayName;
                workspaceDetail.Client.CreatedDate = DateTime.Now.ToString(CultureInfo.InvariantCulture);
                workspaceDetail.Client.ModifiedBy = user.DisplayName;
                workspaceDetail.Client.ModifiedDate = DateTime.Now.ToString(CultureInfo.InvariantCulture);

                string base64Image = String.IsNullOrEmpty(workspaceDetail.ImageLogo)
                                         ? String.Empty
                                         : workspaceDetail.ImageLogo;

                //Call throw web method to create new client.
                SASResultOfstring activateResult = environmentService.Activate(user.DisplayName,
                                                                                    workspaceDetail.Client.ClientID.ToString(CultureInfo.InvariantCulture),
                                                                                    Serialize(workspaceDetail.Client),
                                                                                    Serialize(workspaceDetail.ClientIOFile),
                                                                                    base64Image);
                //validate creating client result
                if (!activateResult.IsSucessful)
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message = activateResult.Message;
                    //bussinessResult.Message = String.Format("Can not active");
                    return bussinessResult;
                }
                #endregion

                if (!activateResult.IsSucessful)
                {
                       bussinessResult.IsSucessful = false;
                    bussinessResult.Message = activateResult.Message;
                    return bussinessResult;
                }

                bussinessResult.IsSucessful = true;
                bussinessResult.OutputResult.Add("AdminUsername", activateResult.OutputResult["AdminUsername"]);
                bussinessResult.OutputResult.Add("AdminPassword", activateResult.OutputResult["AdminPassword"]);
                bussinessResult.OutputResult.Add("ClientName", workspaceDetail.Client.ClientName);
                bussinessResult.OutputResult.Add("ClientId", workspaceDetail.Client.ClientID.ToString(CultureInfo.InvariantCulture));
                bussinessResult.OutputResult.Add("WorkspaceName", workspaceDetail.Workspace.WorkSpaceName);
                bussinessResult.OutputResult.Add("ActivedBy", user.DisplayName);
                bussinessResult.OutputResult.Add("SourceEnv", EnvironmentName.SASEnvironment);
                bussinessResult.OutputResult.Add("TargetEnv", enviromentName);
                bussinessResult.OutputResult.Add("ActivedOn", DateTime.Now.ToShortDateString());
                bussinessResult.OutputResult.Add("url", environmentResult.Result.EnvironmentURL);
             
                #endregion
            }
            catch (Exception serviceException)
            {
                Log(serviceException);
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = String.Format("The Environment Service is not ready for activate function");
                return bussinessResult;
            }

     

        #region 2. Save workspace information for changing - Change status to COMPLETED.

            if (String.CompareOrdinal(workspaceDetail.Workspace.WorkSpaceStatusName, WorkspaceStatus.Completed) != 0)
            {
                workspaceDetail.Workspace.WorkSpaceStatusName = WorkspaceStatus.Completed;
                workspaceDetail.Workspace.EnvironmentName = EnvironmentName.SASEnvironment;
                var returnSASResult = Save(user, workspaceDetail, defaultLogoPath);

                //Validate change status action
                if (!returnSASResult.IsSucessful)
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message = String.Format("Can not change workspace status to COMPLETED");
                    return bussinessResult;
                }
            }
            #endregion

        #region 3. Create new workspace information with status is ACTIVED - ACTIVATE WITHOUT STRIATA.


            if (String.IsNullOrEmpty(workspaceDetail.ClientIOFile.ClientShortName) ||
                String.IsNullOrEmpty(workspaceDetail.ClientIOFile.StriataServerNameOrIP) ||
                String.IsNullOrEmpty(workspaceDetail.ClientIOFile.StriataServerDesc) ||
                String.IsNullOrEmpty(workspaceDetail.ClientIOFile.StriataUsername) ||
                String.IsNullOrEmpty(workspaceDetail.ClientIOFile.FedPayServerNameOrIP) ||
                String.IsNullOrEmpty(workspaceDetail.ClientIOFile.FedPayServerDesc) ||
                String.IsNullOrEmpty(workspaceDetail.ClientIOFile.FedPayUsername))
            {
                workspaceDetail.Workspace.WorkSpaceStatusName = WorkspaceStatus.ActiveWithoutStriata;
            }
            else
            {
                workspaceDetail.Workspace.WorkSpaceStatusName = WorkspaceStatus.Activated;
            }

            //Reset some workspace information to default value to add new workspace record.
            workspaceDetail.Workspace.EnvironmentName = EnvironmentName.SASEnvironment;
            workspaceDetail.Workspace.pkWorkSpace_ID = "0";
            workspaceDetail.Client.pkClient_ID = "0";
            workspaceDetail.ClientIOFile.fkClient_ID = "0";

            SASResult<string> addnewResult = Save(user, workspaceDetail, defaultLogoPath);
            //Validate create new workspace result
            if (!addnewResult.IsSucessful)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = String.Format("Can not add new workspace with status {0}", workspaceDetail.Workspace.WorkSpaceStatusName);
                return bussinessResult;
            }

            //Setup target environment for 'activated' - 'activated without striata' workspace.
            TargetEnvironmentDAO targetEnvironmentDAO = new TargetEnvironmentDAO(user.TokenKey);
            string workspaceId = addnewResult.OutputResult["WorkspaceId"];

            //Set target environment
            SASResult<string> setTargetEnvironmentResult = targetEnvironmentDAO.Save(workspaceId, enviromentName);

            //Validate Set target environment result
            if (!setTargetEnvironmentResult.IsSucessful)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = String.Format("Can not set target environment for workspaceId {0}", workspaceId);
                return bussinessResult;
            }

            #endregion

            return bussinessResult;
        }

        public SASResult<string> ActivateCloneSavedWorkspace(User user, WorkspaceDetail workspaceDetail, ActiavateCloneSaveWorkspace actiavateCloneSaveInfo, string defaultLogoPath)
        {
            //create default for Business result
            SASResult<string> bussinessResult = new SASResult<string>
            {
                IsSucessful = true,
                Result = string.Empty
            };


            #region Validate

            //validate current logged in user.
            if (!ValidateCurrentUser(user, bussinessResult))
            {
                return bussinessResult;
            }

            //validate actiavateCloneSaveInfo

            #endregion

            #region Get current workspace information in SAS database
            SASResult<WorkspaceDetail> workspaceDetailInSASResult = GetClientInformation(user, workspaceDetail.Workspace.pkWorkSpace_ID);
            //validate workspaceDetailInSASResult
            if(!workspaceDetailInSASResult.IsSucessful ||
                workspaceDetailInSASResult.Result == default(WorkspaceDetail))
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Result = string.Empty;
                bussinessResult.Message = "Cannot get current workspace information";
                return bussinessResult;
            }
            #endregion

            #region Deletect selected clone item
            List<string> selectedCloneItem = new List<string>();

            if (String.CompareOrdinal(actiavateCloneSaveInfo.logo, "1") == 0)
            {
                selectedCloneItem.Add(CloneItem.Logo);
            }
            if (String.CompareOrdinal(actiavateCloneSaveInfo.systemPreferences, "1") == 0)
            {
                selectedCloneItem.Add(CloneItem.Preference);
            }
            if (String.CompareOrdinal(actiavateCloneSaveInfo.templates, "1") == 0)
            {
                selectedCloneItem.Add(CloneItem.Template);
            }
            if (String.CompareOrdinal(actiavateCloneSaveInfo.user, "1") == 0)
            {
                selectedCloneItem.Add(CloneItem.User);
                selectedCloneItem.Add(CloneItem.UserNav); //automatically select UserNav
            }
            if (String.CompareOrdinal(actiavateCloneSaveInfo.userRoles, "1") == 0)
            {
                selectedCloneItem.Add(CloneItem.UserRole);
            }
            if (String.CompareOrdinal(actiavateCloneSaveInfo.templateRate, "1") == 0)
            {
                selectedCloneItem.Add(CloneItem.TemplateRate);
            }
            #endregion

            #region Detect source environment service
            SASResult<Core.Entity.Environment> sourceEnvironmentResult = GetEnvironment(user, workspaceDetailInSASResult.Result.Workspace.EnvironmentName);
            //validate sourceEnvironmentResult
            if (!sourceEnvironmentResult.IsSucessful)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = sourceEnvironmentResult.Message;
                return bussinessResult;
            }

            //get target service URL
            string sourceServiceUrl = sourceEnvironmentResult.Result.ServiceUrl;
            //Initialize environment service
            SASServiceClient sourceEnvironmentService = new SASServiceClient(EnpointServiceName, sourceServiceUrl);

            #endregion

            #region Detect target environment service
            
            SASResult<Core.Entity.Environment> targetEnvironmentResult = GetEnvironment(user, actiavateCloneSaveInfo.targetEnvironment);
            //validate targetEnvironment
            if (!targetEnvironmentResult.IsSucessful)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = targetEnvironmentResult.Message;
                return bussinessResult;
            }

            //get target service URL
            string targetServiceUrl = targetEnvironmentResult.Result.ServiceUrl;
            //Initialize environment service
            SASServiceClient targetEnvironmentService = new SASServiceClient(EnpointServiceName, targetServiceUrl);
            
            #endregion

            string cloneId;

            CloneDAO cloneDAO = new CloneDAO(user.TokenKey);

            #region 1.Initialize cloning functions

            SASResult<string> initializeCloningResult = cloneDAO.InitializeCloningProcess(Convert.ToInt32(workspaceDetailInSASResult.Result.Client.ClientID), //clientId
                                                                                            actiavateCloneSaveInfo.workspaceId, //workspaceId
                                                                                            workspaceDetailInSASResult.Result.Workspace.EnvironmentName, //source environment
                                                                                            actiavateCloneSaveInfo.targetEnvironment); //target environment
            //validate initialize
            if (!initializeCloningResult.IsSucessful)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = initializeCloningResult.Message;
                return bussinessResult;
            }
            cloneId = initializeCloningResult.OutputResult["CloneID"];

            #endregion

            #region 2.Get clone items from source environment and save to SAS.
            try
            {
                SASResultOfstring getCloneItemResult = sourceEnvironmentService.GetAppropriateItems(user.DisplayName,
                                                                                                    workspaceDetailInSASResult.Result.Client.ClientID.ToString(CultureInfo.InvariantCulture),
                                                                                                    selectedCloneItem.ToArray());
                //validate getCloneItemResult
                if(!getCloneItemResult.IsSucessful)
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message = getCloneItemResult.Message;
                    return bussinessResult;
                }

                //save to SAS database.
                foreach (var cloneName in selectedCloneItem)
                {
                    string cloneItemContent = getCloneItemResult.OutputResult[cloneName];
                    SASResult<string> addObjectResult = cloneDAO.AddObject(Convert.ToInt32(cloneId), cloneName, cloneItemContent);
                    //validate addObjectResult
                    if(!addObjectResult.IsSucessful)
                    {
                        bussinessResult.IsSucessful = false;
                        bussinessResult.Message = String.Format("Cannot save object {0}", cloneName);
                        return bussinessResult;
                    }
                }


            }
            catch(Exception serviceException)
            {
                Log(serviceException);
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = "Source environment service is not ready";
                return bussinessResult;
            }
            #endregion

            #region 3.Update saved clone items status to InSAS.

            //get all cloned object info
            SASResult<IList<CloneObjectInfo>> getcloneObjectInfoResult = cloneDAO.GetObjectsInfo(Convert.ToInt32(cloneId));
            if (!getcloneObjectInfoResult.IsSucessful || getcloneObjectInfoResult.Result == null)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = "Cannot get cloned object info";
                return bussinessResult;
            }

            //Change status of clone object from INITIAL to INSAS
            foreach (CloneObjectInfo cloneObjectInfo in getcloneObjectInfoResult.Result)
            {
                SASResult<string> modifyStatusResult = cloneDAO.ModifyStatusByToken(cloneObjectInfo.CloneObjectId, CloneStatus.InSAS);
                if(!modifyStatusResult.IsSucessful)
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message = String.Format("Cannot modify status of {0}", cloneObjectInfo.CloneObjectTypeName);
                    return bussinessResult;
                }
            }
            #endregion

            #region 4.Get Objects from SAS database 

            Dictionary<string, string> cloneObjectItems = new Dictionary<string, string>();
            foreach (var cloneItemName in selectedCloneItem)
            {
                SASResult<string> cloneObjectItemResult = cloneDAO.GetObject(Convert.ToInt32(cloneId), cloneItemName);
                if (!cloneObjectItemResult.IsSucessful)
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message = "Cannot get object item from SAS";
                    return bussinessResult;
                }

                cloneObjectItems.Add(cloneItemName, cloneObjectItemResult.OutputResult["XMLString"]);
            }
            
            #endregion

            #region 5.Activate default Client in Target Environment
            try
            {  
                //System preferences cannot be changed
                workspaceDetail.Client.pkClient_ID = "0";
                workspaceDetail.ClientIOFile.fkClient_ID = "0";

                workspaceDetail = DetectInformation(workspaceDetail);
                //Detect connection
                workspaceDetail.Client.StrSubscribeRptUpdate = workspaceDetailInSASResult.Result.Client.SubscribeRptUpdate ? "Yes" : "No";
                workspaceDetail.Client.StrUnsubscribeRptUpdate = workspaceDetailInSASResult.Result.Client.UnsubscribeRptUpdate ? "Yes" : "No";
                workspaceDetail.Client.StrPMOverrideCustomer = workspaceDetailInSASResult.Result.Client.PMOverrideCustomer ? "Yes" : "No";
                workspaceDetail.Client.StrPMAllowIntro = workspaceDetailInSASResult.Result.Client.PMOverrideCustomer ? "Yes" : "No";
                workspaceDetail.Client.StrCustomerStatusTimeOut = workspaceDetailInSASResult.Result.Client.CustomerStatusTimeOut;
                workspaceDetail.Client.StrClientDefaultInfo = workspaceDetailInSASResult.Result.Client.ClientDefaultInfo ? "Yes" : "No";
                workspaceDetail.Client.StrUseClientPaymentMethod = workspaceDetailInSASResult.Result.Client.UseClientPaymentMethod ? "Yes" : "No";

                workspaceDetail.Workspace.EnvironmentName = workspaceDetailInSASResult.Result.Workspace.EnvironmentName;

                string clientXml = Serialize(workspaceDetail.Client);
                string clientIO = Serialize(workspaceDetail.ClientIOFile);

                 //use default logo.
                 MemoryStream memoryStream = new MemoryStream(File.ReadAllBytes(defaultLogoPath));
                workspaceDetail.ImageLogo = ImageStreamToBase64(memoryStream, Path.GetFileName(defaultLogoPath), (int)memoryStream.Length);

                //activate default client information
                SASResultOfstring activateResult = targetEnvironmentService.Activate(user.DisplayName,
                                                                                     workspaceDetailInSASResult.Result.
                                                                                     Workspace.ClientID,
                                                                                     clientXml, clientIO,workspaceDetail.ImageLogo);
                //Validate activate result
                if(!activateResult.IsSucessful)
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message = activateResult.Message;
                    return bussinessResult;
                }
            }
            catch(Exception serviceException)
            {
                Log(serviceException);
            }
            #endregion

            #region 6.Save to Destination Environment
            try
            {
                SASResultOfstring loadObjectResult = targetEnvironmentService.LoadObjectItems(user.DisplayName,
                                                                                              workspaceDetailInSASResult.Result.Workspace.
                                                                                              ClientID, cloneObjectItems);
                //validate load object result.
                if (!loadObjectResult.IsSucessful)
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message = loadObjectResult.Message;
                    return bussinessResult;
                }
            }
            catch (Exception serviceException)
            {
                Log(serviceException);
            }
            #endregion

            #region 7.Update saved clone items status to LoadedDest.
            //Change status of clone object from INITIAL to INSAS
            foreach (CloneObjectInfo cloneObjectInfo in getcloneObjectInfoResult.Result)
            {
                SASResult<string> modifyStatusResult = cloneDAO.ModifyStatusByToken(cloneObjectInfo.CloneObjectId, CloneStatus.LoadedDest);
                if (!modifyStatusResult.IsSucessful)
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message = String.Format("Cannot modify status of {0}", cloneObjectInfo.CloneObjectTypeName);
                    return bussinessResult;
                }
            }
            #endregion

            #region 8.Update status of current workspace from CLONESAVED to CLONECOMPLETE - Update target Environment of workspace
            
            //change the target environment
            TargetEnvironmentDAO targetEnvironmentDAO = new TargetEnvironmentDAO(user.TokenKey);

            workspaceDetailInSASResult.Result.Client.StrSubscribeRptUpdate = workspaceDetailInSASResult.Result.Client.SubscribeRptUpdate ? "Yes" : "No";
            workspaceDetailInSASResult.Result.Client.StrUnsubscribeRptUpdate = workspaceDetailInSASResult.Result.Client.UnsubscribeRptUpdate ? "Yes" : "No";
            workspaceDetailInSASResult.Result.Client.StrPMOverrideCustomer = workspaceDetailInSASResult.Result.Client.PMOverrideCustomer ? "Yes" : "No";
            workspaceDetailInSASResult.Result.Client.StrPMAllowIntro = workspaceDetailInSASResult.Result.Client.PMOverrideCustomer ? "Yes" : "No";
            workspaceDetailInSASResult.Result.Client.StrCustomerStatusTimeOut = workspaceDetailInSASResult.Result.Client.CustomerStatusTimeOut;
            workspaceDetailInSASResult.Result.Client.StrClientDefaultInfo = workspaceDetailInSASResult.Result.Client.ClientDefaultInfo ? "Yes" : "No";
            workspaceDetailInSASResult.Result.Client.StrUseClientPaymentMethod = workspaceDetailInSASResult.Result.Client.UseClientPaymentMethod ? "Yes" : "No";

            SASResult<string> updateTargetEnvironmentResult = targetEnvironmentDAO.Save(workspaceDetailInSASResult.Result.Workspace.pkWorkSpace_ID, actiavateCloneSaveInfo.targetEnvironment);
            //validate update target environment
            if (!updateTargetEnvironmentResult.IsSucessful)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = "Cannot update target environment information";
                return bussinessResult;
            }

            //update status from cloneSaved to Clone completed
            workspaceDetailInSASResult.Result.Workspace.WorkSpaceStatusName = WorkspaceStatus.CloneCompleted;
            SASResult<string> saveWorkspaceResult = Save(user, workspaceDetailInSASResult.Result, defaultLogoPath);
            //validate save workspace result
            if(!saveWorkspaceResult.IsSucessful)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = "Cannot update status of workspace from clone saved to clone completed";
                return bussinessResult;
            }
            
            #endregion

            #region 9.Create a workspace with status ACTIVATED

            workspaceDetail.Workspace.pkWorkSpace_ID = "0";
            workspaceDetail.Workspace.WorkSpaceStatusName = WorkspaceStatus.Activated;
            workspaceDetail.Workspace.WSModifiedBy = user.DisplayName;
            workspaceDetail.Workspace.WSModifiedDate = DateTime.Now;
            workspaceDetail.Workspace.ClientID = workspaceDetail.Client.ClientID.ToString(CultureInfo.InvariantCulture);

            WorkspaceDAO workspaceDAO = new WorkspaceDAO(user.TokenKey);
            SASResult<string> createWorkspaceResult = workspaceDAO.Save(Serialize(workspaceDetail.Workspace), Serialize(workspaceDetail.Client), Serialize(workspaceDetail.ClientIOFile));
            //Validate activate result
            if (!createWorkspaceResult.IsSucessful)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = createWorkspaceResult.Message;
                return bussinessResult;
            }
            //Save logo
            SASResult<string> createWorkspaceLogoResult = workspaceDAO.SetClientLogo(Convert.ToInt32(createWorkspaceResult.OutputResult["WorkspaceId"]), workspaceDetail.ImageLogo);
            //Validate activate result
            if (!createWorkspaceLogoResult.IsSucessful)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = createWorkspaceLogoResult.Message;
                return bussinessResult;
            }

            //set target environment
            SASResult<string> setTargetEnvironment = targetEnvironmentDAO.Save(createWorkspaceResult.OutputResult["WorkspaceId"], actiavateCloneSaveInfo.targetEnvironment);
            //Validate setTargetEnvironment
            if (!setTargetEnvironment.IsSucessful)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = setTargetEnvironment.Message;
                return bussinessResult;
            }

            #endregion
            return bussinessResult;

        }

        /// <summary>
        /// Save the workspace to SAS environment
        /// </summary>
        /// <param name="user"></param>
        /// <param name="workspaceDetail"></param>
        /// <param name="defaultLogoPath"></param>
        /// <returns></returns>
        private SASResult<string> Save(User user, WorkspaceDetail workspaceDetail, string defaultLogoPath)
        {
            //create default for Business result
            SASResult<String> bussinessResult = new SASResult<String>
            {
                IsSucessful = false,
                Result = string.Empty
            };


            #region Validate before save
            //1. Validate email - email format

            //2. Validate phone1, 2 - number

            //3. Validate phone1, 2 - number

            //4. Validate fax - number

            if (workspaceDetail.Client.LogoFileStream != null &&
                workspaceDetail.Client.LogoFileStream.Length > 102400)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = "Image size must be less than 100kb";

                return bussinessResult;
            }

            #endregion

            #region Detect workspace information from submit form data to database data

            //Detect information.
            workspaceDetail = DetectInformation(workspaceDetail);

            //Set default logo for create new workspace only
            if (String.IsNullOrEmpty(workspaceDetail.ImageLogo) && String.CompareOrdinal(workspaceDetail.Workspace.pkWorkSpace_ID, "0") == 0)
            {
                MemoryStream memoryStream = new MemoryStream(File.ReadAllBytes(defaultLogoPath));
                workspaceDetail.ImageLogo = ImageStreamToBase64(memoryStream, Path.GetFileName(defaultLogoPath), (int)memoryStream.Length);
            }

            //update client Id from client schema to workspace information
            workspaceDetail.Workspace.ClientID = workspaceDetail.Client.ClientID.ToString(CultureInfo.InvariantCulture);

            ////when create new workspace, all information about workspace and client will stay in SAS environment
            //workspaceDetail.Workspace.EnvironmentName = EnvironmentName.SASEnvironment;

            //Update log information for workspace
            workspaceDetail.Workspace.WSModifiedBy = user.DisplayName;
            workspaceDetail.Workspace.WSModifiedDate = DateTime.Now;

            //Update log information for client
            if (String.IsNullOrEmpty(workspaceDetail.Client.CreatedBy))
                workspaceDetail.Client.CreatedBy = user.DisplayName;

            if (String.IsNullOrEmpty(workspaceDetail.Client.CreatedDate)) 
                workspaceDetail.Client.CreatedDate = DateTime.Now.ToString(CultureInfo.InvariantCulture);

            workspaceDetail.Client.ModifiedBy = user.DisplayName;
            workspaceDetail.Client.ModifiedDate = DateTime.Now.ToString(CultureInfo.InvariantCulture);


            //Serialize to get workspace data as XML format
            string workspaceSchemaXmlData = Serialize(workspaceDetail.Workspace);

            //Serialize to get client data as XML format
            string clientSchemaXmlData = Serialize(workspaceDetail.Client);

            //Serialize to get client data as XML format
            string sasClientSchemaXmlData = Serialize(workspaceDetail.ClientIOFile);

            #endregion

            #region Save data to database

            //Call to Data access layer 
            WorkspaceDAO workspaceDao = new WorkspaceDAO(user.TokenKey);

            //Save data
            SASResult<string> createWorkspaceResult = workspaceDao.Save(workspaceSchemaXmlData, clientSchemaXmlData, sasClientSchemaXmlData);

            if (!createWorkspaceResult.IsSucessful)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = createWorkspaceResult.Message;

                return bussinessResult;
            }

            int workspaceId = Convert.ToInt32(createWorkspaceResult.OutputResult["WorkspaceId"]);
            bussinessResult.OutputResult.Add("WorkspaceId", workspaceId.ToString(CultureInfo.InvariantCulture));

            //if new workspace is created then insert it's logo.
            if (createWorkspaceResult.IsSucessful && !String.IsNullOrEmpty(workspaceDetail.ImageLogo))
            {
                //Save workspace logo
                SASResult<string> result = workspaceDao.SetClientLogo(workspaceId, workspaceDetail.ImageLogo);

                if (!result.IsSucessful)
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message = createWorkspaceResult.Message;

                    return bussinessResult;
                }
            }

            #endregion

            bussinessResult.IsSucessful = true;
            return bussinessResult;
        }

        #endregion

        #region Cloning 

        /// <summary>
        /// Create a workspace with status cloneSaved
        /// </summary>
        /// <param name="user"></param>
        /// <param name="workspaceId"></param>
        /// <param name="defaultLogoPath"></param>
        /// <returns></returns>
        public SASResult<string> Cloning(User user, string workspaceId, string defaultLogoPath)
        {
            //create default for Business result
            SASResult<String> bussinessResult = new SASResult<String>
            {
                IsSucessful = false,
                Result = string.Empty,
                Message = String.Empty
            };

            #region Validate

            //validate current logged in user.
            if (!ValidateCurrentUser(user, bussinessResult))
            {
                return bussinessResult;
            }
            #endregion

            SASResult<WorkspaceDetail> workspaceResult = GetClientInformation(user, workspaceId);
            //validate workspace result
            if (!workspaceResult.IsSucessful || workspaceResult.Result == default(WorkspaceDetail))
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = "Cannot get workspace information";
                return bussinessResult;
            }

            //The workspace selected to clone must be an activated or activated without Striata workspace 
            if(String.CompareOrdinal(workspaceResult.Result.Workspace.WorkSpaceStatusName, WorkspaceStatus.Activated) == 0 ||
               String.CompareOrdinal(workspaceResult.Result.Workspace.WorkSpaceStatusName, WorkspaceStatus.ActiveWithoutStriata) == 0)
            {
                WorkspaceDetail workspaceDetail = workspaceResult.Result;

                //Get target environment of workspace
                TargetEnvironmentDAO targetEnvironmentDAO = new TargetEnvironmentDAO(user.TokenKey);
                SASResult<string> getTargetEnvironmentResult = targetEnvironmentDAO.Get(workspaceDetail.Workspace.pkWorkSpace_ID);
                //Validate getTargetEnvironmentResult
                if(!getTargetEnvironmentResult.IsSucessful)
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message = "Cannot get target environment of selected workspace";
                    return bussinessResult;
                }

                //set target environment to source environment.
                workspaceDetail.Workspace.EnvironmentName = getTargetEnvironmentResult.OutputResult["TargetEnvironment"];

                //set workspace status to clone saved.
                workspaceDetail.Workspace.WorkSpaceStatusName = WorkspaceStatus.CloneSaved;

                //reset pkWorkSpace_ID.
                workspaceDetail.Workspace.pkWorkSpace_ID = "0";

                //reset pkClient_ID.
                workspaceDetail.Client.pkClient_ID = "0";

                //reset fkClient_ID.
                workspaceDetail.ClientIOFile.fkClient_ID = "0";

                //set default logo.
                MemoryStream memoryStream = new MemoryStream(File.ReadAllBytes(defaultLogoPath));
                workspaceDetail.ImageLogo = ImageStreamToBase64(memoryStream, Path.GetFileName(defaultLogoPath), (int)memoryStream.Length);


                ////when create new workspace, all information about workspace and client will stay in SAS environment
                //workspaceDetail.Workspace.EnvironmentName = EnvironmentName.SASEnvironment;

                //Update log information for workspace
                workspaceDetail.Workspace.WSModifiedBy = user.DisplayName;
                workspaceDetail.Workspace.WSModifiedDate = DateTime.Now;

                //Update log information for client
                if (String.IsNullOrEmpty(workspaceDetail.Client.CreatedBy))
                    workspaceDetail.Client.CreatedBy = user.DisplayName;

                if (String.IsNullOrEmpty(workspaceDetail.Client.CreatedDate))
                    workspaceDetail.Client.CreatedDate = DateTime.Now.ToString(CultureInfo.InvariantCulture);

                workspaceDetail.Client.ModifiedBy = user.DisplayName;
                workspaceDetail.Client.ModifiedDate = DateTime.Now.ToString(CultureInfo.InvariantCulture);


                //Serialize to get workspace data as XML format
                string workspaceSchemaXmlData = Serialize(workspaceDetail.Workspace);

                //Serialize to get client data as XML format
                string clientSchemaXmlData = Serialize(workspaceDetail.Client);

                //Serialize to get client data as XML format
                string sasClientSchemaXmlData = Serialize(workspaceDetail.ClientIOFile);

                //Call to Data access layer 
                WorkspaceDAO workspaceDao = new WorkspaceDAO(user.TokenKey);

                //Save data
                SASResult<string> createWorkspaceResult = workspaceDao.Save(workspaceSchemaXmlData, clientSchemaXmlData, sasClientSchemaXmlData);

                if (!createWorkspaceResult.IsSucessful)
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message = createWorkspaceResult.Message;

                    return bussinessResult;
                }

                int newWorkspaceId = Convert.ToInt32(createWorkspaceResult.OutputResult["WorkspaceId"]);
                bussinessResult.OutputResult.Add("WorkspaceId", workspaceId.ToString(CultureInfo.InvariantCulture));

                //if new workspace is created then insert it's logo.
                if (createWorkspaceResult.IsSucessful && !String.IsNullOrEmpty(workspaceDetail.ImageLogo))
                {
                    //Save workspace logo
                    SASResult<string> result = workspaceDao.SetClientLogo(newWorkspaceId, workspaceDetail.ImageLogo);

                    if (!result.IsSucessful)
                    {
                        bussinessResult.IsSucessful = false;
                        bussinessResult.Message = createWorkspaceResult.Message;
                        return bussinessResult;
                    }
                }

                
                //return business result.
                return bussinessResult;
            }

            bussinessResult.IsSucessful = false;
            bussinessResult.Message = "Cannot clone a workspace that has not been activated";
            return bussinessResult;
        }
        #endregion

        #region Validate workspace
        /// <summary>
        /// Validate a client is existed in a specific environment by clientId or not.
        /// </summary>
        /// <param name="user"></param>
        /// <param name="clientId">client id</param>
        /// <param name="targetEnvironmentName">specific environment</param>
        /// <returns></returns>
        public SASResult<bool> ValidateActiveClientId(User user, string clientId, string targetEnvironmentName)
        {
            //create default for Business result
            SASResult<bool> bussinessResult = new SASResult<bool>
            {
                IsSucessful = false,
                Result = false
            };

            #region Validate

            //validate current logged in user.
            if (!ValidateCurrentUser(user, bussinessResult))
            {
                return bussinessResult;
            }

            #endregion

            const string sortCondition = "CreatedDate desc";
            string condition = String.Format(" AND (ClientID = '{0}' and TargetEnvName = '{1}')", clientId, targetEnvironmentName);

            //Call to DAL to get search result
            WorkspaceDAO workspaceDao = new WorkspaceDAO(user.TokenKey);
            SASResult<IList<WorkspaceSummary>> dataAccessResult = workspaceDao.GetSummary(1, Int32.MaxValue, sortCondition, condition);

            if (dataAccessResult.IsSucessful)
            {
                //Validate the inputted clientId is existed on any target environment or not.
                IEnumerable<string> listTargetEnvironmentName = dataAccessResult.Result.Select(workspace => workspace.TargetEnvironmentName.ToLower()).Distinct();
                if (!listTargetEnvironmentName.Contains(targetEnvironmentName.ToLower()))
                {
                    bussinessResult.IsSucessful = true;
                    bussinessResult.Result = true;
                }
                else
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Result = false;
                    bussinessResult.Message = String.Format("This client is already existed on {0} environment", targetEnvironmentName);
                }
            }
            else
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Result = false;
                bussinessResult.Message = "Can not perform validate action";
            }


            return bussinessResult;
        }

        /// <summary>
        /// Validate workspace name when user add new a workspace.
        /// </summary>
        /// <param name="user"></param>
        /// <param name="workSpaceName">workspace name to validate</param>
        /// <returns></returns>
        public SASResult<bool> ValidateInsertWorkspaceName(User user, string workSpaceName)
        {
            //create default for Business result
            SASResult<bool> bussinessResult = new SASResult<bool>
            {
                IsSucessful = false,
                Result = false
            };

            #region Validate
            //validate current logged in user.
            if (!ValidateCurrentUser(user, bussinessResult))
            {
                return bussinessResult;
            }

            #endregion

            const string sortCondition = "CreatedDate desc";
            string condition = String.Format(" AND (WorkSpaceName = '{0}')", workSpaceName);

            WorkspaceDAO workspaceDao = new WorkspaceDAO(user.TokenKey);
            SASResult<IList<WorkspaceSummary>> dataAccessResult = workspaceDao.GetSummary(1, Int32.MaxValue, sortCondition, condition);

            if (dataAccessResult.IsSucessful)
            {
                IEnumerable<string> listWorkspaceName = dataAccessResult.Result.Select(workspace => workspace.WorkspaceName.ToLower()).Distinct();
                if (!listWorkspaceName.Contains(workSpaceName.ToLower()))
                {
                    bussinessResult.IsSucessful = true;
                    bussinessResult.Result = true;
                }
                else
                {
                    bussinessResult.IsSucessful = true;
                    bussinessResult.Result = false;
                    bussinessResult.Message = String.Format("this workspace name is existed");
                }
            }
            else
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Result = false;
                bussinessResult.Message = "Can not perform validate action";
            }


            return bussinessResult;
        }

        public SASResult<bool> ValidateInsertClientId(User user, string clientId)
        {
            //create default for Business result
            SASResult<bool> bussinessResult = new SASResult<bool>
            {
                IsSucessful = false,
                Result = false
            };

            #region Validate
            //validate current logged in user.
            if (!ValidateCurrentUser(user, bussinessResult))
            {
                return bussinessResult;
            }

            #endregion

            const string sortCondition = "CreatedDate desc";
            string condition = String.Format(" AND (ClientID = '{0}')", clientId);

            WorkspaceDAO workspaceDao = new WorkspaceDAO(user.TokenKey);
            SASResult<IList<WorkspaceSummary>> dataAccessResult  = workspaceDao.GetSummary(1, Int32.MaxValue, sortCondition, condition);

            if (!dataAccessResult.IsSucessful)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Result = false;
                bussinessResult.Message = "Can not perform validate action";
                return bussinessResult;
            }
            if (dataAccessResult.Result.Count > 0)
            {
                bussinessResult.IsSucessful = true;
                bussinessResult.Result = false;
                bussinessResult.Message = "ClientId is existed";
                return bussinessResult;
            }

            bussinessResult.IsSucessful = true;
            bussinessResult.Result = true;
            bussinessResult.Message = String.Empty;
            return bussinessResult;
        }

        public SASResult<bool> ValidateUpdateWorkspaceName(User user,string workspaceId, string workSpaceName)
        {
            //create default for Business result
            SASResult<bool> bussinessResult = new SASResult<bool>
            {
                IsSucessful = false,
                Result = false
            };

            #region Validate
            //validate current logged in user.
            if (!ValidateCurrentUser(user, bussinessResult))
            {
                return bussinessResult;
            }

            #endregion

            const string sortCondition = "CreatedDate desc";
            string condition = String.Format(" AND (WorkSpaceName = '{0}' AND pkWorkSpace_ID <> {1})", workSpaceName, workspaceId);

            WorkspaceDAO workspaceDao = new WorkspaceDAO(user.TokenKey);
            SASResult<IList<WorkspaceSummary>> dataAccessResult = workspaceDao.GetSummary(1, Int32.MaxValue, sortCondition, condition);

            if(!dataAccessResult.IsSucessful)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Result = false;
                bussinessResult.Message = "Can not perform validate action";
                return bussinessResult;
            }

            IList<WorkspaceSummary> listWorkspaceSummary = dataAccessResult.Result;

            IEnumerable<int> listClientId = listWorkspaceSummary.Select(workspace => workspace.ClientId).Distinct();
            if (listClientId.Count() > 1)
            {
                bussinessResult.IsSucessful = true;
                bussinessResult.Result = false;
                bussinessResult.Message = String.Format("this workspace name is existed");
                return bussinessResult;
            }

            bussinessResult.IsSucessful = true;
            bussinessResult.Result = true;
            bussinessResult.Message = string.Empty;
            return bussinessResult;
        }

        /// <summary>
        /// 
        /// </summary>
        /// <param name="user"></param>
        /// <param name="clientShortName"></param>
        /// <param name="targetEnvironment"></param>
        /// <returns></returns>
        public SASResult<bool> ValidateActivateClientShortName(User user, string clientShortName, string targetEnvironment)
        {
            //create default for Business result
            SASResult<bool> bussinessResult = new SASResult<bool>
            {
                IsSucessful = false,
                Result = false
            };

            SASResult<Core.Entity.Environment> environmentResult = GetEnvironment(user, targetEnvironment);
            //Validate environment result
            if (!environmentResult.IsSucessful)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = environmentResult.Message;
                bussinessResult.Result = false;
                return bussinessResult;
            }

            //Get environment service URL from environment result
            var environmentServiceURL = environmentResult.Result.ServiceUrl;

            //Initialize environment service
            SASServiceClient environmentService = new SASServiceClient(EnpointServiceName, environmentServiceURL);

            try
            {
                SASResultOfstring serviceResult = environmentService.GetClientId(clientShortName, user.DisplayName);

                if (serviceResult.IsSucessful)
                {
                    if (String.IsNullOrEmpty(serviceResult.OutputResult["ClientID"]))
                    {
                        bussinessResult.IsSucessful = true;
                        bussinessResult.Result = true;
                        bussinessResult.Message = String.Empty;
                    }
                    else
                    {
                        bussinessResult.IsSucessful = true;
                        bussinessResult.Result = false;
                        bussinessResult.Message = "Client short name is existed on selected environment";
                    }
                }
                else
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message = serviceResult.Message;
                }
            }
            catch (Exception serviceException)
            {
                Log(serviceException);
                bussinessResult.IsSucessful = false;
                bussinessResult.Result = false;
                bussinessResult.Message = String.Format("The Environment Service is not ready for validate function");
            }

            return bussinessResult;
        }

        /// <summary>
        /// Validate shortName is existed or not
        /// </summary>
        /// <param name="user"></param>
        /// <param name="clientId"></param>
        /// <param name="targetEnvironment"></param>
        /// <param name="clientShortName"></param>
        /// <returns></returns>
        public SASResult<bool> ValidateUpdateClientShortName(User user, string clientId, string targetEnvironment, string clientShortName)
        {
            //create default for Business result
            SASResult<bool> bussinessResult = new SASResult<bool>
            {
                IsSucessful = false,
                Result = false
            };

            SASResult<Core.Entity.Environment> environmentResult = GetEnvironment(user, targetEnvironment);
            //Validate environment result
            if (!environmentResult.IsSucessful)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = environmentResult.Message;
                bussinessResult.Result = false;
                return bussinessResult;
            }

            //Get environment service URL from environment result
            string environmentServiceURL = environmentResult.Result.ServiceUrl;

            //Initialize environment service
            SASServiceClient environmentService = new SASServiceClient(EnpointServiceName, environmentServiceURL);

            try
            {
                SASResultOfstring serviceResult = environmentService.GetClientIdByShortName(user.DisplayName, clientShortName);

                if (!serviceResult.IsSucessful)
                {
                    bussinessResult.IsSucessful = false;
                    bussinessResult.Message = serviceResult.Message;
                    return bussinessResult;
                }

                if(String.IsNullOrEmpty(serviceResult.OutputResult["ClientID"]) || //the shortname is not existed in target environment
                    String.CompareOrdinal(serviceResult.OutputResult["ClientID"], clientId) == 0) //the shortname 
                {
                    bussinessResult.IsSucessful = true;
                    bussinessResult.Result = true;
                    return bussinessResult;
                }

                bussinessResult.IsSucessful = true;
                bussinessResult.Result = false;
                bussinessResult.Message = String.Format("Client shortname is existed in {0} environment", targetEnvironment);
                return bussinessResult;
                
            }
            catch (Exception serviceException)
            {
                Log(serviceException);
                bussinessResult.IsSucessful = false;
                bussinessResult.Result = false;
                bussinessResult.Message = String.Format("The Environment Service is not ready for validate function");
            }

            return bussinessResult;


        }
        #endregion

        /// <summary>
        /// 
        /// </summary>
        /// <param name="user"></param>
        /// <param name="mailSettings"></param>
        /// <param name="emailTemplatePath"></param>
        /// <param name="defaultAdminInfo"></param>
        /// <returns></returns>
        public SASResult<bool> SendDefaultAdminInfomation(User user, MailSettingsSectionGroup mailSettings, string emailTemplatePath, DefaultAdminInfo defaultAdminInfo)
        {
            //create default for Business result
            SASResult<bool> bussinessResult = new SASResult<bool>
                                                    {
                                                        IsSucessful = false,
                                                        Result = false
                                                    };

            #region Validate

            //validate current logged in user.
            if (!ValidateCurrentUser(user, bussinessResult))
            {
                return bussinessResult;
            }

            if (mailSettings == null || string.IsNullOrEmpty(emailTemplatePath))
            {
                bussinessResult.IsSucessful = true;
                bussinessResult.Result = false;
                bussinessResult.Message = "Can not load smtp mail information to send email";
                return bussinessResult;
            }

            if(defaultAdminInfo == null)
            {
                bussinessResult.IsSucessful = true;
                bussinessResult.Result = false;
                bussinessResult.Message = "Can not get default admin information";
                return bussinessResult;
            }

            #endregion

            string emailContent = File.ReadAllText(emailTemplatePath);

            emailContent = emailContent.Replace("##targetEnv##", defaultAdminInfo.TargetEnv). //fill target environment information
                                        Replace("##sourceEnv##", defaultAdminInfo.SourceEnv). //fill source environment information
                                        Replace("##clientId##", defaultAdminInfo.ClientID).   //fill clientId information
                                        Replace("##clientName##", defaultAdminInfo.ClientName). //fill clientName information
                                        Replace("##workspaceName##", defaultAdminInfo.WorkspaceName). //fill workspace name information
                                        Replace("##activatedBy##", defaultAdminInfo.ActivedBy). //fill activate by information
                                        Replace("##activatedOn##", defaultAdminInfo.ActivedOn). //fill activate on information
                                        Replace("##adminUser##", defaultAdminInfo.AdminUserName). //fill admin user information
                                        Replace("##adminPassword##", defaultAdminInfo.AdminPassword). //fill admin password information
                                        Replace("##dpmUrl##", defaultAdminInfo.Url); ////fill DPM URL information

            string fromEmail = mailSettings.Smtp.From;
            MailMessage mailMessage = new MailMessage(fromEmail, defaultAdminInfo.ToEmailAdress)
                {
                    IsBodyHtml = true,
                    Body = emailContent,
                    Subject = String.Format("Please note that {0} has been activated for {1}", defaultAdminInfo.WorkspaceName, defaultAdminInfo.ClientName),
                };

            try
            {
                var smtp = new SmtpClient(mailSettings.Smtp.Network.Host, mailSettings.Smtp.Network.Port)
                {
                    EnableSsl = mailSettings.Smtp.Network.EnableSsl,
                    DeliveryMethod = SmtpDeliveryMethod.Network,
                    UseDefaultCredentials = mailSettings.Smtp.Network.DefaultCredentials,
                    Credentials = new NetworkCredential(mailSettings.Smtp.Network.UserName, mailSettings.Smtp.Network.Password)
                };

                //send activate mail
                smtp.Send(mailMessage);
                bussinessResult.IsSucessful = true;
                bussinessResult.Result = true;
            }
            catch (SmtpFailedRecipientException failedRecipientException)
            {
                Log(failedRecipientException);
                bussinessResult.IsSucessful = true;
                bussinessResult.Result = false;
                bussinessResult.Message = "Wrong email address";
                return bussinessResult;
            }
            catch (SmtpException smtpException)
            {
                Log(smtpException);
                bussinessResult.IsSucessful = true;
                bussinessResult.Result = false;
                bussinessResult.Message = "Can not send email due to smtp configuration";
                return bussinessResult;
            }
           
            return bussinessResult;
        }

        /// <summary>
        /// Get all environment name
        /// </summary>
        /// <param name="user"></param>
        /// <returns></returns>
        public SASResult<IList<string>> GetEnvironmentNames(User user)
        {
            //create default for Business result
            SASResult<IList<string>> bussinessResult = new SASResult<IList<string>>
                {
                    IsSucessful = false,
                    Message = String.Empty,
                    Result = new List<string>()
                };

            #region Validate
            //validate current logged in user.
            if (!ValidateCurrentUser(user, bussinessResult))
            {
                return bussinessResult;
            }
            #endregion


            //Call to data access layer to get data
            EnvironmentDAO environmentDAO = new EnvironmentDAO(user.TokenKey);
            SASResult<IList<string>> dataAccessResult = environmentDAO.GetEnvironmentList();

            //Validate data package and get the data value
            if(!dataAccessResult.IsSucessful)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = dataAccessResult.Message;
                return bussinessResult;
            }

            
            //Remove SAS environment
            if (dataAccessResult.Result.Any(item => item.Contains(EnvironmentName.SASEnvironment)))
                dataAccessResult.Result.Remove(EnvironmentName.SASEnvironment);

            bussinessResult.IsSucessful = true;
            bussinessResult.Result = dataAccessResult.Result;

            return bussinessResult;
        } 
        
        /// <summary>
        /// Detect and filter workspace detail information before save workspace.
        /// </summary>
        /// <param name="workspaceDetail"></param>
        /// <returns></returns>
        private WorkspaceDetail DetectInformation(WorkspaceDetail workspaceDetail)
        {
            //Detect payment method

            if (workspaceDetail.Client.ClientID == 0)
            {
                workspaceDetail.Client.ClientID = Convert.ToInt32(workspaceDetail.Client.StrClientId);    
            }

            workspaceDetail.Client.WebPayment = String.IsNullOrEmpty(workspaceDetail.Client.StrWebPayment) ? "N" : "Y"; 
            workspaceDetail.Client.ACHPayment = String.IsNullOrEmpty(workspaceDetail.Client.StrACHPayment) ? "N" : "Y"; 
            workspaceDetail.Client.DebitPayment = String.IsNullOrEmpty(workspaceDetail.Client.StrDebitPayment) ? "N" : "Y"; 
            workspaceDetail.Client.CreditPayment = String.IsNullOrEmpty(workspaceDetail.Client.StrCreditPayment) ? "N" : "Y"; 
            workspaceDetail.Client.VISA = String.IsNullOrEmpty(workspaceDetail.Client.StrVISA) ? "N" : "Y"; 
            workspaceDetail.Client.Mastercard = String.IsNullOrEmpty(workspaceDetail.Client.StrMastercard) ? "N" : "Y"; 
            workspaceDetail.Client.AMEX = String.IsNullOrEmpty(workspaceDetail.Client.StrAMEX) ? "N" : "Y"; 
            workspaceDetail.Client.Discover = String.IsNullOrEmpty(workspaceDetail.Client.StrDiscover) ? "N" : "Y"; 
          
            //Detect connection
            workspaceDetail.Client.SubscribeRptUpdate = workspaceDetail.Client.StrSubscribeRptUpdate != "No";
            workspaceDetail.Client.UnsubscribeRptUpdate = workspaceDetail.Client.StrUnsubscribeRptUpdate != "No";
            workspaceDetail.Client.PMOverrideCustomer = workspaceDetail.Client.StrPMOverrideCustomer != "No";
            workspaceDetail.Client.PMAllowIntro = workspaceDetail.Client.StrPMAllowIntro != "No";
            workspaceDetail.Client.CustomerStatusTimeOut = String.IsNullOrEmpty(workspaceDetail.Client.StrCustomerStatusTimeOut)
                                                                    ? "0" : workspaceDetail.Client.StrCustomerStatusTimeOut;
            workspaceDetail.Client.ClientDefaultInfo = workspaceDetail.Client.StrClientDefaultInfo != "No";
            workspaceDetail.Client.UseClientPaymentMethod = workspaceDetail.Client.StrUseClientPaymentMethod != "No";

            workspaceDetail.ClientIOFile.TimeRunner = "0";

            //Convert logo stream to base64 string
            if (workspaceDetail.Client.LogoFileStream != null && workspaceDetail.Client.LogoFileStream.Length > 0)
            {
                workspaceDetail.ImageLogo = ImageStreamToBase64(workspaceDetail.Client.LogoFileStream, workspaceDetail.Client.LogoFileName, workspaceDetail.Client.LogoFileStreamSize);    
            }
            
            return workspaceDetail;
        }

        /// <summary>
        /// Get environment service URL from environment name.
        /// </summary>
        /// <param name="user"></param>
        /// <param name="environmentName"></param>
        /// <returns></returns>
        private SASResult<Core.Entity.Environment> GetEnvironment(User user, string environmentName)
        {
            //create default for Business result
            SASResult<Core.Entity.Environment> bussinessResult = new SASResult<Core.Entity.Environment>
            {
                IsSucessful = true,
                Result = null
            };

            string condition = String.Format(" AND (EnvironmentName = '{0}')", environmentName);
            
            EnvironmentDAO environmentDAO = new EnvironmentDAO(user.TokenKey);
            SASResult<IList<Core.Entity.Environment>> environmentResult = environmentDAO.GetEnvironments(1, 100, "[EnvironmentName]", condition);

            if (!environmentResult.IsSucessful)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = environmentResult.Message;
                return bussinessResult;
            }

            Core.Entity.Environment selectedEnvironment = environmentResult.Result.FirstOrDefault();

            //if inputted environment is not in list.
            if (selectedEnvironment == null)
            {
                bussinessResult.IsSucessful = false;
                bussinessResult.Message = String.Format("Can not get {0} environment information", environmentName);
                return bussinessResult;
            }

            bussinessResult.IsSucessful = true;
            bussinessResult.Result = selectedEnvironment;

            return bussinessResult;
        }
    }
}